home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1999 July: Technology Seed / ADC Seed CD - July 1999.toast / USB / Mac OS USB DDK v1.2 / Examples / PrinterClassDriver / usbprint.c < prev    next >
Encoding:
C/C++ Source or Header  |  1999-04-15  |  7.1 KB  |  355 lines  |  [TEXT/MPS ]

  1. /*
  2.     File:        usbprint.c
  3.  
  4.     Contains:    usb printer class device communication
  5.                     (installed in UnitTable)
  6.  
  7.     Version:    xxx put version here xxx
  8.  
  9.  
  10.  
  11.     Copyright: 1998 by Apple Computer, Inc., all rights reserved.
  12.  
  13. */
  14. #include "PrinterClassDriver.h"
  15.  
  16. #ifndef __DEVICES__
  17. #include <devices.h>
  18. #endif
  19.  
  20. #ifndef __FILES__
  21. #include <files.h>
  22. #endif
  23.  
  24. #define kMaskLowByte    0x0FF
  25.  
  26. extern pascal OSErr    DRVRDone( OSErr err, DCtlPtr ctl, IOParamPtr pb );
  27. static void AbortActive( CntrlParam *pb, DCtlPtr clt );
  28.  
  29. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  30.     Name:        GetPrinterStruct
  31.  
  32.     Input Parameters:    IOParamPtr        i/o parameter block
  33.         
  34.     Output Parameters:
  35.         usbPrinterPBStruct    * pointer to the device
  36.         
  37.     Description:
  38.         Given a device control block, map it to a usb device's data structure
  39.  
  40.  
  41.  
  42. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  43. static struct usbPrinterPBStruct    *
  44. GetPrinterStruct( DCtlPtr ctl )
  45. {
  46.     return (struct usbPrinterPBStruct *) ctl->dCtlStorage;
  47. }
  48.  
  49. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  50.     Name:        Read
  51.  
  52.     Input Parameters:
  53.         
  54.     Output Parameters:
  55.         <none>
  56.         
  57.     Description:
  58.         
  59.  
  60.  
  61.  
  62.  
  63. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  64. static OSErr
  65. Read (IOParamPtr pb, DCtlPtr ctl)
  66. {
  67.     struct usbPrinterPBStruct    *usbprint = GetPrinterStruct( ctl );
  68.  
  69.     //
  70.     //    if we have a unidirectional interface
  71.     //        report a read error
  72.     //        (only status supported by unidirectional is Centronics compatible)
  73.     //
  74.     pb->ioResult = paramErr;    // assume bad
  75.  
  76.     if ( usbprint != nil )
  77.     {
  78.         if ( usbprint->printerProtocol == kUSBPrinterUnidirectionalProtocol )
  79.             pb->ioResult = readErr;
  80.             
  81.         else if (usbprint->terminating)
  82.             pb->ioResult = abortErr;    
  83.             
  84.         else if (usbprint->qread)
  85.             (*usbprint->qread)( pb, ctl, usbprint );    //    map the read param block into the usb param block
  86.     }
  87.     return pb->ioResult;
  88.  
  89. }
  90.  
  91. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  92.     Name:        Write
  93.  
  94.     Input Parameters:
  95.         
  96.     Output Parameters:
  97.         <none>
  98.         
  99.     Description:
  100.         
  101.  
  102.  
  103.  
  104.  
  105. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  106. static OSErr
  107. Write (IOParamPtr pb, DCtlPtr ctl)
  108. {
  109.     struct usbPrinterPBStruct    *usbprint = GetPrinterStruct( ctl );
  110.  
  111.     pb->ioResult = paramErr;    // assume bad
  112.  
  113.     if ( usbprint != nil )
  114.     {
  115.         if (usbprint->terminating)
  116.             pb->ioResult = abortErr;
  117.             
  118.         else if (usbprint->qwrite)
  119.             (*usbprint->qwrite)( pb, ctl, usbprint );    //    map the write param block into the usb param block
  120.     }
  121.     return pb->ioResult;
  122. }
  123.  
  124. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  125.     Name:        AbortActive
  126.  
  127.     Input Parameters:
  128.         pb
  129.         ctl
  130.         
  131.     Output Parameters:
  132.         <none>
  133.         
  134.     Description:
  135.         
  136.  
  137.  
  138. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  139. static void
  140. AbortActive( CntrlParam *pb, DCtlPtr ctl )
  141. {
  142.     //        we need to wait here until the transaction is complete
  143.     struct usbPrinterPBStruct    *usbprint = GetPrinterStruct( ctl );
  144.     struct USBPB                    *pActiveUSBIO;
  145.     IOParamPtr                        pActiveIO;
  146.  
  147.     if ( usbprint != nil )
  148.     {
  149.         if ( pb->ioCRefNum == usbprint->outRefNum )
  150.         {
  151.             pActiveUSBIO = &usbprint->out;
  152.             pActiveIO = usbprint->writeDrvr.pb;
  153.         }
  154.         else
  155.         {
  156.             pActiveUSBIO = &usbprint->in;
  157.             pActiveIO = usbprint->readDrvr.pb;
  158.         }
  159.         
  160.         if ( pActiveUSBIO->usbCompletion != nil )
  161.         {
  162.             if (usbprint->qabort != nil )
  163.                 (*usbprint->qabort)( pb->ioCRefNum, usbprint );    //    cancel outstanding transactions
  164.             //
  165.             //    synchronize data toggle
  166.             // USB addendum, the endpoints of the pipe may be out of sync
  167.             //    a soft reset in the printer class should restore the data toggle
  168.             //
  169.             if (!(usbprint->terminating) && (usbprint->qstatus != nil))
  170.             {
  171.                 pb->csCode = kDrvrSoftReset;
  172.                 (*usbprint->qstatus)( pb, ctl, usbprint );
  173.             }
  174.         }
  175.     }
  176. }
  177.  
  178. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  179.     Name:        DRVROpen
  180.  
  181.     Input Parameters:
  182.         
  183.     Output Parameters:
  184.         <none>
  185.         
  186.     Description:
  187.         
  188.  
  189.  
  190. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  191.  
  192. pascal OSErr
  193. DRVROpen(CntrlParam *pb, DCtlPtr dce)
  194. {
  195.     return noErr;
  196. }
  197.  
  198. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  199.     Name:        DRVRClose
  200.  
  201.     Input Parameters:
  202.         
  203.     Output Parameters:
  204.         <none>
  205.         
  206.     Description:
  207.         
  208.  
  209.  
  210. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  211.  
  212. pascal OSErr
  213. DRVRClose(CntrlParam *pb, DCtlPtr ctl)
  214. {
  215.     return noErr;
  216. }
  217.  
  218. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  219.     Name:        DRVRStatus
  220.  
  221.     Input Parameters:
  222.         
  223.     Output Parameters:
  224.         <none>
  225.         
  226.     Description:
  227.         
  228.  
  229.  
  230.  
  231.  
  232. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  233.  
  234. pascal OSErr
  235. DRVRStatus(CntrlParam *pb, DCtlPtr ctl)
  236. {
  237.     OSErr                err;
  238.     struct             usbPrinterPBStruct    *usbprint = GetPrinterStruct( ctl );
  239.  
  240.     pb->ioResult = paramErr;
  241.     if ( usbprint != nil )
  242.     {
  243.         if (usbprint->terminating)
  244.             pb->ioResult = abortErr;    
  245.         else
  246.         {
  247.             switch ( pb->csCode )
  248.             {
  249.                 case kDrvrCentronicsStatus:        //  USB device: centronics status
  250.                 case kDrvr1284IdString:             //  USB device: 1284 capability string
  251.                 case kDrvrSoftReset:                    //  USB device: soft reset
  252.                     if ( usbprint->qstatus )
  253.                         (*usbprint->qstatus)( pb, ctl, usbprint );    //    map the status param block into the usb param block
  254.                     break;
  255.                 case kDrvrNumDevices:    
  256.                     pb->ioResult =  noErr;
  257.                     break;
  258.                 case 1:    
  259.                 case 2:                                    // deprecated
  260.                 default:
  261.                     pb->ioResult = paramErr;
  262.                     break;
  263.             }
  264.         }
  265.     }
  266.     return pb->ioResult;
  267. }
  268.  
  269. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  270.     Name:        DRVRControl
  271.  
  272.     Input Parameters:
  273.         csCode                        csParam
  274.         ------                        -------
  275.         kDrvrPrivateSetStorage    pointer to the USB device class storage
  276.  
  277.     Output Parameters:
  278.         <none>
  279.         
  280.     Description:
  281.         
  282.  
  283.  
  284.  
  285.  
  286.  
  287.  
  288. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  289.  
  290. pascal OSErr
  291. DRVRControl(CntrlParam *pb, DCtlPtr ctl)
  292. {
  293.     OSErr                                err            = noErr;
  294.     struct usbPrinterPBStruct    *usbprint    = GetPrinterStruct( ctl );
  295.  
  296.     switch ( pb->csCode )
  297.     {
  298.     case killCode:
  299.         //
  300.         //    killIO is always handled as an immediate mode transaction
  301.         //
  302.         AbortActive( pb, ctl );
  303.         break;
  304.     case kDrvrPrivateSetStorage:
  305.         //
  306.         //    reference the class driver's private storage
  307.         //        it's not a handle, but devices.h thinks it should be
  308.         //
  309.         ctl->dCtlStorage = (Handle) *((Ptr *) &pb->csParam[0] );
  310.         break;
  311.     default:
  312.         err = paramErr;
  313.         break;
  314.     }
  315.     return err;
  316. }
  317.  
  318. /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  319.     Name:        DRVRPrime
  320.  
  321.     Input Parameters:
  322.         
  323.     Output Parameters:
  324.         <none>
  325.         
  326.     Description:
  327.         
  328.  
  329.  
  330. ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
  331.  
  332. pascal OSErr
  333. DRVRPrime(CntrlParam *pb, DCtlPtr ctl)
  334. {
  335.     OSErr    err = paramErr;
  336.     //
  337.     //    switch on the low order byte to dispatch reads and writes
  338.     //
  339.     if ( (pb->ioTrap & kMaskLowByte) == aRdCmd )
  340.         err = Read( (IOParamPtr) pb, ctl );
  341.         
  342.     else if ( (pb->ioTrap & kMaskLowByte) == aWrCmd )
  343.         err = Write( (IOParamPtr) pb, ctl );
  344.  
  345.     //
  346.     //    get the ioResult in case the completion routine has already executed
  347.     //    
  348.     if ( err == noErr )
  349.         err = pb->ioResult;
  350.  
  351.     return err;
  352. }
  353.  
  354. // eof
  355.